package cn.samler.shopapi.Service.impl;

import cn.samler.shopapi.Entity.Cart;
import cn.samler.shopapi.Entity.Spec;
import cn.samler.shopapi.Entity.SpecItem;
import cn.samler.shopapi.Entity.User;
import cn.samler.shopapi.Mapper.CartMapper;
import cn.samler.shopapi.Model.Request.Cart.Goods;
import cn.samler.shopapi.Model.Request.Cart.CartModel;
import cn.samler.shopapi.Model.Response.Goods.GoodsDetails;
import cn.samler.shopapi.Model.Sys.ServiceResult;
import cn.samler.shopapi.Service.CartService;
import cn.samler.shopapi.Service.GoodsService;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import org.springframework.stereotype.Service;

import java.util.*;

@Service
public class CartServiceImpl implements CartService {
    private CartMapper cartMapper;
    private GoodsService goodsService;

    CartServiceImpl(CartMapper cartMapper, GoodsService goodsService) {
        this.cartMapper = cartMapper;
        this.goodsService = goodsService;
    }

    @Override
    public Cart find(int uid, Goods goods) {
        return cartMapper.getCart(uid, goods.getGid(), goods.getSpecToken());
    }

    @Override
    public Cart findByToken(int uid, int gid, String token) {
        return cartMapper.getCart(uid, gid, token);
    }

    @Override
    public JSONArray findAll(int uid) {
        JSONArray jsonArray = new JSONArray();
        List<Cart> cart = cartMapper.listAll(uid);
        cart.forEach(item -> {
            JSONObject json = new JSONObject();
            GoodsDetails goods = goodsService.getGoodsById(item.getGid());
            List<HashMap<String, Object>> specArray = new ArrayList<>();
            item.getSpec().forEach((specId, itemId) -> {
                Spec spec = goodsService.getSpecById(item.getGid(), Integer.parseInt(specId));
                SpecItem specItem = goodsService.getSpecItemById(Integer.parseInt(specId), itemId);
                specArray.add(new HashMap<String, Object>() {
                    {
                        this.put("id", spec.getId());
                        this.put("name", spec.getName());
                        this.put("item", new HashMap<String, Object>() {
                            {
                                this.put("id", specItem.getItemId());
                                this.put("name", specItem.getName());
                            }
                        });
                    }
                });
            });
            json.putAll(new HashMap<String, Object>() {
                {
                    this.put("id", goods.getId());
                    this.put("name", goods.getName());
                    this.put("src", goods.getImage());
                    this.put("spec", specArray);
                    this.put("spec_token", item.getSpecToken());
                    this.put("number", item.getNumber());
                    this.put("price", goods.getPrice());
                }
            });
            jsonArray.add(json);
        });

        return jsonArray;
    }

    @Override
    public ServiceResult add(int uid, Goods goods) {
        // 数量为0直接返回成功
        if (goods.getNumber() == 0)
            return ServiceResult.success();

        // 判断对应的规格是否归属于该商品
        Iterator<Map.Entry<String, Integer>> specSet = goods.getSpec().entrySet().iterator();
        while (specSet.hasNext()) {
            Map.Entry<String, Integer> item = specSet.next();
            if (!this.checkSpec(goods.getGid(), Integer.parseInt(item.getKey()), item.getValue()))
                return ServiceResult.failure("商品规格不存在");
        }

        // 购物车中无对应商品且数量小于0时返回成功
        Cart cart = this.find(uid, goods);
        if (cart == null && goods.getNumber() < 0)
            return ServiceResult.success();

        if (cart != null && cart.getSpecToken().equals(goods.getSpecToken())) {
            Integer number = cart.getNumber() + goods.getNumber();
            if (number > 0) {
                // 商品数量增
                goods.setNumber(number);
                return this.update(uid, goods) ? ServiceResult.success() : ServiceResult.failure("更新失败");
            }
            // 删除商品
            return this.remove(uid, goods) ? ServiceResult.success() : ServiceResult.failure("删除失败");
        }
        // 添加商品
        return cartMapper.addCart(uid, goods) ? ServiceResult.success() : ServiceResult.failure("添加失败");
    }

    @Override
    public ServiceResult updateNumber(User user, CartModel updateNumber) {
        if (updateNumber.getNumber() <= 0)
            return ServiceResult.failure("数量错误");

        Cart cart = cartMapper.getCart(user.getId(), updateNumber.getGid(), updateNumber.getSpecToken());
        if (cart == null)
            return ServiceResult.failure("未找到对应数据");

        Goods goods = new Goods();
        goods.setGid(updateNumber.getGid());
        goods.setSpec(cart.getSpec());
        goods.setNumber(updateNumber.getNumber());
        if (cartMapper.updateCart(user.getId(), goods))
            return ServiceResult.success();

        return ServiceResult.failure(cart.getNumber());
    }

    @Override
    public boolean remove(int uid, Goods goods) {
        return cartMapper.removeCart(uid, goods);
    }

    @Override
    public boolean removeByToken(int uid, int gid, String token) {
        return cartMapper.removeCartByToken(uid, gid, token);
    }

    @Override
    public boolean update(int uid, Goods goods) {
        return cartMapper.updateCart(uid, goods);
    }

    @Override
    public boolean checkSpec(int gid, int sid, int itemId) {
        Integer realGid = cartMapper.findGidBySpec(sid, itemId);
        return realGid != null && realGid == gid;
    }
}
